package org.mentalsmash.crossroads;

import java.io.FileNotFoundException;
import java.io.FileReader;

import org.apache.log4j.Logger;
import org.apache.log4j.PropertyConfigurator;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.json.JSONTokener;


public class Configuration {
	
	private final static Logger log = Logger.getLogger(Configuration.class);
	private final static String CONFIGURATION_FILE = "conf/crossroads.conf";
	
	private final static String LOG4J_KEY = "log4j-configuration-file";
	private final static String WEBHARVEST_KEY = "web-harvest-configuration-file";
	private final static String WEBHARVEST_WRK_KEY = "web-harvest-work-dir";
	private final static String HTTP_TIMEOUT_KEY = "http-timeout-millis";
	private final static String ENCODING_KEY = "character-encoding";
	private final static String SCHEMA_EXT_KEY = "default-schema-file-extension";
	private final static String DEF_EXT_KEY = "default-definitions-file-extension";
	private final static String LEXER_KEY = "path-to-lexer-theory";
	private final static String PARSER_KEY = "path-to-parser-theory";
	private final static String BUILDER_KEY = "path-to-builder-theory";
	private final static String XSL_PATH_KEY = "path-to-filter-stylesheet";
	private final static String DICTIONARY_SIZE_KEY = "definition-dictionary-size";
	private final static String LANG_KEY = "crossword-language";
	private final static String LARGE_RESULT_KEY = "large-google-result-set";
	private final static String GOOGLE_KEY = "google-api-key";
	private final static String REF_DOMAIN_KEY = "google-ref-domain";
	private final static String IGNORED_EXTENSIONS = "ignored-extensions";
	
	
	//General configuration
	private  String _log4jConf = "conf/log4j.conf";
	private  String _webHarvestConf = "conf/web-harvest.conf";
	private long _httpTimeout = 10000;
	private String _webHarvestWorkDir = "tmp/";
	private  String _encoding = "utf-8";
	
	
	//Parser configuration
	private  String _schemaExtension = "schema";
	private  String _defintionsExtension = "def";
	
	private  String _lexerTheoryPath = "theories/crossroads_lexer.pdb";
	private  String _parserTheoryPath = "theories/crossroads_parser.pdb";
	private  String _builderTheoryPath = "theories/crossroads_builder.pdb";

	//Solver configuration
	private  String _xhtmlFilterStylesheet = "pick_body.xsl";
	private  int _dictionarySize = 25;
	private  String _language = "it";
	
	//Web search configuration

	private boolean _largeGoogleSearch = false;
	private String _googleApiKey = "ABQIAAAASfE0W3TlKVsczDye1estrhQSDv4kZOu2P-hcKMqixU9JvYgb1BTBv7I1FZabmQVwS1YNN6wLlofu0g";
	private String _referenceDomain = "http://mentalsmash.org";
	private String[] _ignoreExtensions = new String[] {".doc",".pdf",".docx",".ppt",".pptx"};
	
	

	private static Configuration _instance;
	
	private Configuration(){
		parseConfiguration();
		
	}
	
	public static Configuration getInstance(){
		if(_instance == null)
			_instance = new Configuration();
		return _instance;
	}
	
	private void parseConfiguration() {
		JSONTokener tkn = null;
		try {
			tkn = new JSONTokener(new FileReader(CONFIGURATION_FILE));
		} catch (FileNotFoundException e1) {
			System.err.println("Cannot find configuration file.");
			System.exit(-1);
		}
		JSONObject confFile = null;
		try {
			confFile = new JSONObject(tkn);
			
		} catch (JSONException e) {
			System.err.println("Error building configuration json object. " + e.getMessage() +  " Loading defaults...");
			return;
		}
		
		//configuring log4j
		try {
			setLog4jConf(confFile.getString(LOG4J_KEY));
			PropertyConfigurator.configure(getLog4jConf());
		} catch (JSONException e) {
			System.err.println("Can't find log4j conf.");
		}
		
		try{ 
			setWebHarvestConf(confFile.getString(WEBHARVEST_KEY));
			setWebHarvestWorkDir(confFile.getString(WEBHARVEST_WRK_KEY));
			setHttpTimeout(confFile.getLong(HTTP_TIMEOUT_KEY));
			setEncoding(confFile.getString(ENCODING_KEY));
			setSchemaExtension(confFile.getString(SCHEMA_EXT_KEY));
			setDefintionsExtension(confFile.getString(DEF_EXT_KEY));
			setLexerTheoryPath(confFile.getString(LEXER_KEY));
			setParserTheoryPath(confFile.getString(PARSER_KEY));
			setBuilderTheoryPath(confFile.getString(BUILDER_KEY));

			setXhtmlFilterStylesheet(confFile.getString(XSL_PATH_KEY));
			setDictionarySize(confFile.getInt(DICTIONARY_SIZE_KEY));
			setLanguage(confFile.getString(LANG_KEY));

			setLargeGoogleSearch(confFile.getBoolean(LARGE_RESULT_KEY));
			setGoogleApiKey(confFile.getString(GOOGLE_KEY));
			setReferenceDomain(confFile.getString(REF_DOMAIN_KEY));

			JSONArray ignoredExt = confFile.getJSONArray(IGNORED_EXTENSIONS);
			String[] ign = new String[ignoredExt.length()];
			for(int i =0 ; i<ignoredExt.length();i++)
				ign[i] = ignoredExt.getString(i);
			setIgnoreExtensions(ign);
		}
		catch(JSONException e){
			log.warn("Unable to read some property from conf file. " + e.getMessage());
		}
		
		
	}


	public String getLog4jConf() {
		return _log4jConf;
	}

	public String getEncoding() {
		return _encoding;
	}

	public String getDefintionsExtension() {
		return _defintionsExtension;
	}

	public String getLexerTheoryPath() {
		return _lexerTheoryPath;
	}

	public String getParserTheoryPath() {
		return _parserTheoryPath;
	}

	public String getBuilderTheoryPath() {
		return _builderTheoryPath;
	}

	public int getDictionarySize() {
		return _dictionarySize;
	}

	public String getLanguage() {
		return _language;
	}

	public boolean isLargeGoogleSearch() {
		return _largeGoogleSearch;
	}

	public String getGoogleApiKey() {
		return _googleApiKey;
	}

	public String getReferenceDomain() {
		return _referenceDomain;
	}

	public String getSchemaExtension() {
		return _schemaExtension;
	}

	public String getXhtmlFilterStylesheet() {
		return _xhtmlFilterStylesheet;
	}
	
	public String[] getIgnoreExtensions() {
		return _ignoreExtensions;
	}

	public void setLog4jConf(String log4jConf) {
		_log4jConf = log4jConf;
	}

	public void setEncoding(String encoding) {
		_encoding = encoding;
	}

	public void setSchemaExtension(String schemaExtension) {
		_schemaExtension = schemaExtension;
	}

	public void setDefintionsExtension(String defintionsExtension) {
		_defintionsExtension = defintionsExtension;
	}

	public void setLexerTheoryPath(String lexerTheoryPath) {
		_lexerTheoryPath = lexerTheoryPath;
	}

	public void setParserTheoryPath(String parserTheoryPath) {
		_parserTheoryPath = parserTheoryPath;
	}

	public void setBuilderTheoryPath(String builderTheoryPath) {
		_builderTheoryPath = builderTheoryPath;
	}

	public void setXhtmlFilterStylesheet(String xhtmlFilterStylesheet) {
		_xhtmlFilterStylesheet = xhtmlFilterStylesheet;
	}

	public void setDictionarySize(int dictionarySize) {
		_dictionarySize = dictionarySize;
	}

	public void setLanguage(String language) {
		_language = language;
	}

	public void setLargeGoogleSearch(boolean largeGoogleSearch) {
		_largeGoogleSearch = largeGoogleSearch;
	}

	public void setGoogleApiKey(String googleApiKey) {
		_googleApiKey = googleApiKey;
	}

	public void setReferenceDomain(String referenceDomain) {
		_referenceDomain = referenceDomain;
	}

	public void setIgnoreExtensions(String[] ignoreExtensions) {
		_ignoreExtensions = ignoreExtensions;
	}

	public void setWebHarvestConf(String webHarvestConf) {
		_webHarvestConf = webHarvestConf;
	}

	public String getWebHarvestConf() {
		return _webHarvestConf;
	}

	public void setWebHarvestWorkDir(String webHarvestWorkDir) {
		_webHarvestWorkDir = webHarvestWorkDir;
	}

	public String getWebHarvestWorkDir() {
		return _webHarvestWorkDir;
	}

	public void setHttpTimeout(long httpTimeout) {
		_httpTimeout = httpTimeout;
	}

	public long getHttpTimeout() {
		return _httpTimeout;
	}
	
	
}
